"""
使用方法：
C:\Windows\system32>F:
F:\>cd F:\code\python\test
F:\code\python\test>
"""


import subprocess
import os
import time
from pynput.keyboard import Key, Controller
import pyautogui
from datetime import datetime, timedelta
import tkinter as tk
import threading
import ctypes
import pygetwindow


# Define the SYSTEMTIME structure
class SYSTEMTIME(ctypes.Structure):
    _fields_ = [("wYear", ctypes.c_ushort),
                ("wMonth", ctypes.c_ushort),
                ("wDayOfWeek", ctypes.c_ushort),
                ("wDay", ctypes.c_ushort),
                ("wHour", ctypes.c_ushort),
                ("wMinute", ctypes.c_ushort),
                ("wSecond", ctypes.c_ushort),
                ("wMilliseconds", ctypes.c_ushort)]


# Load the Windows Library
windll = ctypes.windll.kernel32


# Function to set system time
def set_system_time(timestr):
    # Parse the time string

    hours, minutes, seconds = map(int, timestr.split(':'))
    # 东八区时间
    adjusted_hours = hours - 8
    if adjusted_hours < 0:
        adjusted_hours += 24
    # Create a SYSTEMTIME object
    system_time = SYSTEMTIME()
    system_time.wYear = 2024
    system_time.wMonth = 2
    system_time.wDay = 15
    system_time.wHour = adjusted_hours
    system_time.wMinute = minutes
    system_time.wSecond = seconds
    system_time.wMilliseconds = 0

    # Set system time
    windll.SetSystemTime(ctypes.byref(system_time))

#mouse = Controller()
keyboard = Controller()
# 创建一个停止事件
stop_event = threading.Event()
pause_event = threading.Event()
images_path = "d:\\"
global musouProcess
global zuobiProcess
musou_thread = None
global offset_second
global difficulty
global specific_times
# 设置系统时间的函数
#def set_system_time(timestr):
#    os.system('time ' + timestr)

# 创建一个线程，接收线程消息，消息内容为timestr
global time_adjustment_thread
global time_adjustment_queue
musou_time = ""

def zuobiqi():
    app_title = ".:|| aSxDox ||:."  # 替换为实际的程序窗口标题
    try:
        app_window = pygetwindow.getWindowsWithTitle(app_title)[0]
        app_window.activate()
    except IndexError:
        print(f"未找到标题为'{app_title}'的窗口")
    time.sleep(1)

    # 返回到musouProcess的主界面
    keyboard.press(Key.alt)
    keyboard.press(Key.tab)

    time.sleep(0.1)
    keyboard.release(Key.alt)
    keyboard.release(Key.tab)


def transZuobiqi():
    #zuobiqi()

    time.sleep(4)
    print_message("f5全无效")
    send(Key.f5)
    thread_sleep(1)
    print_message("f10一击必杀")
    send(Key.f10)
    thread_sleep(1)


def time_adjustment_worker():
    print_message("时间暂停器启动")
    global musou_time
    while True:
        set_system_time(musou_time)
        time.sleep(0.90)  # Sleep for 990 milliseconds to prevent high CPU usage
        if pause_event.is_set():
            pause_event.clear()
            break

def start_time_adjustment_thread():
    global time_adjustment_thread
    time_adjustment_thread = threading.Thread(target=time_adjustment_worker)
    time_adjustment_thread.start()

def adjust_time_list(time_list):
    new_time_list = []
    for time_str in time_list:
        hour, minute, second = map(int, time_str.split(':'))
        if 16 <= minute <= 21 or 32 <= minute <= 37 or 48 <= minute <= 53:
            minute -= 6
        if 16 <= second <= 21 or 32 <= second <= 37 or 48 <= second <= 53:
            second -= 6
        new_time_list.append(f"{hour:02d}:{minute:02d}:{second:02d}")
    return new_time_list

def convert_time_list(time_list):
    time_list = time_list.strip().split('\n')
    time_list = [time.strip() for time in time_list if time.strip()]
    new_list = adjust_time_list(time_list)
    return new_list

def thread_sleep(n):
    if stop_event.is_set():
        print_message("游戏已经结束了，你个老6，你可以重新开始了")
        stop_event.clear()
        exit(0)
    time.sleep(n)

def get_timestring():
    current_time = datetime.now()

    # 将时间格式化为HHMMSS形式的字符串
    time_string = current_time.strftime("%H%M%S")

    return time_string

def press_hold_time(key, sec):
    keyboard.press(key)
    thread_sleep(sec)
    keyboard.release(key)

def send(key):
    keyboard.press(key)
    thread_sleep(0.1)
    keyboard.release(key)
    thread_sleep(0.1)

def skip_start():
    # 此处仍然有3-5秒播放，是为了确保准确率。系统不一定每次都是一样的速度启动游戏。系统快可以设置低，慢的话可以设置为25，或者更大
    thread_sleep(20)
    print_message("跳过开头动画")
    send(Key.enter)
    thread_sleep(3)

def press_any_key():
    # 进入主菜单，等待时间为6秒
    print_message("按任意键进入主菜单")
    send(Key.enter)
    thread_sleep(5)

def select_free_mode():
    send(Key.up)
    print_message("选择自由模式")
    thread_sleep(1)
    send(Key.enter)
    print_message("进入自由模式")
    thread_sleep(5)

def select_level():
    select_free_mode()

    #选择战役
    print_message("选择千里走单骑")
    send(Key.right)
    thread_sleep(1)
    send(Key.down)
    thread_sleep(1)
    send(Key.down)
    thread_sleep(1)
    send(Key.down)
    thread_sleep(1)
    send(Key.down)
    thread_sleep(1)
    send(Key.enter)
    thread_sleep(3)

    send(Key.enter)
    thread_sleep(2)

    #选择难度
    if difficulty == "困难":
        print_message("选择困难")
        send(Key.right)
        thread_sleep(1)
    elif difficulty == "入门":
        print_message("选择入门")
        send(Key.left)
        thread_sleep(1)
        send(Key.left)
        thread_sleep(1)
    else:
        print_message("选择普通")

    send(Key.enter)
    thread_sleep(5)

    #选择武将，按5次->，选择诸葛亮，每一次Key.right都会向右移动一次，选择下一个武将
    send(Key.f12)

    # 赵云
    thread_sleep(1)
    # 关羽
    send(Key.right)
    thread_sleep(1)
    # 张飞
    print_message("选择张飞")
    send(Key.right)
    thread_sleep(1)
    # 诸葛亮
    #print_message("选择诸葛亮")
    #send(Key.right)
    #thread_sleep(1)
    send(Key.enter)
    thread_sleep(3)

    #选择2p
    print_message("选择赵云")
    send(Key.enter)
    thread_sleep(5)

def prepare():
    # 1p战斗准备
    print_message("1p战斗准备")
    send(Key.enter)
    thread_sleep(2)
    send(Key.up)
    thread_sleep(2)
    send(Key.enter)
    thread_sleep(2)

    # 1p选择护卫
    print_message("选择护卫")
    send(Key.enter)
    thread_sleep(2)

    # 1p返回
    send(Key.esc)
    thread_sleep(2)
    send(Key.esc)
    thread_sleep(2)

    # 1p战斗准备
    send(Key.up)
    thread_sleep(2)
    send(Key.enter)
    thread_sleep(1)

    print_message("2p战斗准备")
    send(Key.enter)
    thread_sleep(2)
    send(Key.up)
    thread_sleep(2)
    send(Key.enter)
    thread_sleep(2)

    # 2p选择护卫
    print_message("选择护卫")
    send(Key.down)
    thread_sleep(1)
    send(Key.enter)
    thread_sleep(2)

    # 1p返回
    send(Key.esc)
    thread_sleep(2)
    send(Key.esc)
    thread_sleep(2)

def start_game():
    # 开始战斗
    send(Key.up)
    thread_sleep(2)
    print_message("开始战斗")
    send(Key.enter)

    thread_sleep(5)
    send(Key.esc)
    print_message("跳过开场动画")
    thread_sleep(2)


def create_images_path():
    global images_path
    current_dir = os.getcwd()
    # 创建保存路径
    images_path = os.path.join(current_dir, 'images')

    # 创建images文件夹
    os.makedirs(images_path, exist_ok=True)
    print_message("武器截图目录：" + images_path)

def save_weapon_image(name):
    global images_path
    screenshot = pyautogui.screenshot(region=(500, 200, 1200, 600))
    print_message("武器截图：" + images_path + "\\" + name)
    screenshot.save(images_path + "\\" + name)

def musou(timestr):
    global musouProcess
    global images_path
    global musou_time
    global zuobiProcess

    if difficulty == "普通":
        dif = "c"
    elif difficulty == "入门":
        dif = "a"
    else:
        dif = "d"

    imagename = timestr.replace(':', '') + dif + '.jpg'
    imagename2p = timestr.replace(':', '') + '-2' + dif + '.jpg'

    # app1 = subprocess.Popen("D:\Program Files\\Notepad--\\Notepad--.exe")
    # app = Application().start("D:\\娱乐\\真三国无双4S\\musou.exe")
    # app = Application().start("D:\Program Files\\Notepad--\\Notepad--.exe")
    musou_time = timestr
    print_message("设置时间" + musou_time)
    thread_sleep(1)
    exe_dir = os.path.dirname(images_path)
    os.chdir(exe_dir)
    zuobiProcess = subprocess.Popen(exe_dir + "\\zuobi.exe")
    thread_sleep(offset_second)
    musouProcess = subprocess.Popen(exe_dir + "\\musou.exe")

    #os.chdir("D:\\娱乐\\真三国无双4S")
    #musouProcess = subprocess.Popen("D:\\娱乐\\真三国无双4S\\musou.exe")
    # 完全打开
    skip_start()

    #===press any key
    press_any_key()

    #选择战役
    select_level()

    #战斗准备
    prepare()

    start_game()

    transZuobiqi()

    #调整到防御
    #send(Key.enter)
    #thread_sleep(1)
    thread_sleep(1)
    if offset_second > 2:
        print_message("低配配置电脑")
        thread_sleep(3)

    print_message("正前方视角")
    send('l')
    thread_sleep(1)

    print_message("走1.6秒")
    press_hold_time('w', 1.6)
    thread_sleep(1.5)

    print_message("右转")
    send('d')
    thread_sleep(1.5)

    print_message("正前方视角")
    send('l')
    thread_sleep(1)

    print_message("走14秒")
    press_hold_time('w', 15)
    send(Key.space)
    thread_sleep(1)
    print_message("秒关羽")
    for i in range(20):
        send('m')
        thread_sleep(1)

    print_message("战斗胜利")
    thread_sleep(40)
    print_message("1p确认功勋")
    send(Key.enter) # 功勋确认

    thread_sleep(5)
    print_message("1p确认级别")
    send(Key.enter) # 级别
    thread_sleep(5)

    #武器情况
    print_message("1p武器截图保存")
    save_weapon_image(imagename)
    thread_sleep(1)
    send(Key.enter)
    thread_sleep(1)
    send(Key.enter)

    thread_sleep(4)
    print_message("1p护卫功勋")
    send(Key.enter)

    thread_sleep(10)
    print_message("2p确认功勋")
    send(Key.enter)

    thread_sleep(3)
    print_message("2p确认级别")
    send(Key.enter)  # 级别
    thread_sleep(2)

    # 武器情况
    print_message("2p武器截图保存")
    save_weapon_image(imagename2p)
    thread_sleep(2)
    musouProcess.terminate()
    zuobiProcess.terminate()
    pause_event.clear()



def exist_in(time_string, time_array):
    # 遍历时间列表中的每个时间字符串
    for t in time_array:
        # 判断当前时间字符串的前 5 个字符（小时和分钟）是否与时间列表中的对应部分匹配
        if t.startswith(time_string[:5]):
            return True
    return False

def isImageExist(timestr):
    global images_path
    if difficulty == "普通":
        dif = "c"
    elif difficulty == "入门":
        dif = "a"
    else:
        dif = "d"

    imagename = timestr.replace(':', '') + dif + '.jpg'
    return os.path.exists(images_path + "\\" + imagename)

def convert_time_list(time_list):
    time_list = time_list.strip().split('\n')
    time_list = [time.strip() for time in time_list if time.strip()]
    new_list = adjust_time_list(time_list)
    return new_list

def exist_in(time_string, time_array):
    # 遍历时间列表中的每个时间字符串
    for t in time_array:
        # 判断当前时间字符串的前 5 个字符（小时和分钟）是否与时间列表中的对应部分匹配
        if t.startswith(time_string[:5]):
            return True
    return False

def run_spec(sp_times):
    time_array = convert_time_list(sp_times)
    for t in time_array:
        if isImageExist(t):
            print_message(t + "已经存在，跳过")
            continue
        print_message(t + "打一把")
        musou(t)
        thread_sleep(5)
        if stop_event.is_set():
            stop_event.clear()
            break
def run(startpoint, endpoint):
    create_images_path()

    if specific_times.strip():
        run_spec(specific_times)
        return
    # 将输入的时间字符串转换为 datetime 格式
    start_time = datetime.strptime(startpoint, "%H:%M:%S")
    end_time = datetime.strptime(endpoint, "%H:%M:%S")

    # 设置起始时间为当天的午夜 00:00:00
    current_date = datetime.now().replace(hour=0, minute=0, second=0, microsecond=0)
    start_time = current_date.replace(hour=start_time.hour, minute=start_time.minute, second=start_time.second)
    print_message("起始时间：" + start_time.strftime("%H:%M:%S"))

    # 设置结束时间为当天的午夜 23:59:59
    end_time = current_date.replace(hour=end_time.hour, minute=end_time.minute, second=end_time.second)
    print_message("结束时间：" + end_time.strftime("%H:%M:%S"))
    print_message("三国无双启动速度：" + str(offset_second))

    # 遍历所有秒数，并打印为时间
    current_time = start_time
    while current_time <= end_time and not stop_event.is_set():
        if (current_time.minute < 16 or current_time.minute > 21) and \
                (current_time.minute < 32 or current_time.minute > 37) and \
                (current_time.minute < 48 or current_time.minute > 53) and \
                (current_time.second < 16 or current_time.second > 21) and \
                (current_time.second < 32 or current_time.second > 37) and \
                (current_time.second < 48 or current_time.second > 53):
            timestr = current_time.strftime("%H:%M:%S")
            if isImageExist(timestr):
                print_message(timestr + "已经存在，跳过")
                current_time += timedelta(seconds=1)
                continue
            print_message(timestr + "打一把")
            musou(timestr)
            # 统计时间
            now = datetime.now()
            delta = now - current_time
            hours, minutes, seconds = str(delta).split(':')
            print_message(f"用时：{hours}:{minutes}:{seconds}秒")
            thread_sleep(5)

        current_time += timedelta(seconds=1)
        if stop_event.is_set():
            stop_event.clear()
            break


def run_script():
    global musou_thread
    global offset_second
    global musou_time
    global difficulty
    global specific_times
    if musou_thread is not None and musou_thread.is_alive():
        # 将之前的线程设置为守护线程
        musou_thread.daemon = True
        musou_thread = None
    start_time = start_entry.get()
    end_time = end_entry.get()
    offset_second = int(offset_entry.get())
    difficulty = difficulty_var.get()
    specific_times = specific_time_box.get("1.0", tk.END)
    musou_thread = threading.Thread(target=run, args=(start_time, end_time))
    musou_thread.start()
    musou_time = "00:00:00"
    start_time_adjustment_thread()

def stop_script():
    global musou_thread
    musouProcess.terminate()
    zuobiProcess.terminate()
    stop_event.set()
    pause_event.set()
    if musou_thread:
        musou_thread.join(timeout=2)
        if musou_thread.is_alive():
            musou_thread._delete()
    if time_adjustment_thread:
        time_adjustment_thread._delete()

    print_message('需要等待, 提示”游戏已经结束了，你个老6, 你可以重新开始了“之后，才能再次开始')

def print_message(msg):
    text_box.insert(tk.END, msg + '\n')
    text_box.see(tk.END)

root = tk.Tk()
root.title('Musou刷武器')
root.geometry('400x500')


# 创建标签和输入框组件
start_time_container = tk.Frame(root)
start_time_container.pack(side=tk.TOP)
start_label = tk.Label(start_time_container, text='起始时间（hh:mm:ss）')
start_label.pack(side=tk.LEFT)

start_entry = tk.Entry(start_time_container)
start_entry.insert(0, '08:00:00')
start_entry.pack(side=tk.LEFT)

end_time_container = tk.Frame(root)
end_time_container.pack(side=tk.TOP)
end_label = tk.Label(end_time_container, text='结束时间（hh:mm:ss）')
end_label.pack(side=tk.LEFT)

end_entry = tk.Entry(end_time_container)
end_entry.insert(0, '08:00:01')
end_entry.pack(side=tk.LEFT)

#创建难度选项
# 增加难度选项
difficulty_container = tk.Frame(root)
difficulty_container.pack(side=tk.TOP)
difficulty_label = tk.Label(difficulty_container, text='难度选择:')
difficulty_label.pack(side=tk.LEFT)

difficulty_var = tk.StringVar(root)
difficulty_var.set("困难")
difficulty_options = ["入门", "普通", "困难"]
difficulty_menu = tk.OptionMenu(difficulty_container, difficulty_var, *difficulty_options)
difficulty_menu.pack(side=tk.LEFT)

# 创建运行按钮组件
# 创建容器
button_container = tk.Frame(root)
button_container.pack(side=tk.TOP)

offset_label = tk.Label(button_container, text='无双程序启动速度(秒)')
offset_label.pack(side=tk.LEFT)

offset_entry = tk.Entry(button_container, width=10)
offset_entry.insert(0, '1')
offset_entry.pack(side=tk.LEFT)


run_button = tk.Button(button_container, text='开始', command=run_script)
run_button.pack(side=tk.LEFT)

# 创建结束按钮组件
stop_button = tk.Button(button_container, text='结束', command=stop_script)
stop_button.pack(side=tk.LEFT)


# 创建标签和输入框组件
specific_time_container = tk.Frame(root)
specific_time_container.pack(side=tk.TOP, fill=tk.BOTH, expand=True)

exclude_time_label = tk.Label(specific_time_container, text="指定时间点：")
exclude_time_label.pack(side=tk.LEFT, fill=tk.X)

# 创建滚动信息栏
specific_time_scrollbar = tk.Scrollbar(specific_time_container)
specific_time_scrollbar.pack(side=tk.RIGHT, fill=tk.Y)

# 创建文本框
specific_time_box = tk.Text(specific_time_container, yscrollcommand=specific_time_scrollbar.set, height=10, width=40)
specific_time_box.pack(side=tk.LEFT, fill=tk.BOTH, expand=True)
#specific_time_box.insert(tk.END, "00:00:00")

# 将滚动信息栏关联到文本框
specific_time_scrollbar.config(command=specific_time_box.yview)


# 创建容器
text_box_container = tk.Frame(root)
text_box_container.pack(side=tk.TOP, fill=tk.BOTH, expand=True)

# 创建滚动信息栏
scrollbar = tk.Scrollbar(text_box_container)
scrollbar.pack(side=tk.RIGHT, fill=tk.Y)

# 创建文本框
text_box = tk.Text(text_box_container, yscrollcommand=scrollbar.set, height=10, width=50)
text_box.pack(side=tk.LEFT, fill=tk.BOTH, expand=True)

# 将滚动信息栏关联到文本框
scrollbar.config(command=text_box.yview)

root.mainloop()
